v1.81.0.0 feat: Aside is the browser gstack drives first; every browsing skill, the PDF/diagram renderer, and web research; the bundled browser stays the automatic fallback - #2810
Merged
Conversation
… resolvers
{{ASIDE_SETUP}} (readiness probe + ten rules for driving the user's real browser), {{ASIDE_COOKBOOK}} (script shapes verified live against Aside CLI 1.26: one flow per aside repl script, CDP console hook before navigation, evidence lines, session-directory artifact handoff, GSTACK_STEP_OK sentinel), {{ASIDE_RESEARCH}} (research through aside exec, WebSearch when Aside is absent, knowledge otherwise) and {{BROWSE_FALLBACK}} (the fifteen-row Aside-step to $B-command table plus the rules that differ, so every browsing skill keeps working on gstack's own headless browser). test/aside-driver.test.ts pins the sentences and asserts every browsing skill carries the Aside block followed by the fallback; test/helpers/aside-available.ts is the shared live-Aside probe.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…r as fallback lib/aside-render.ts serves the HTML's directory on loopback (Aside refuses file:// URLs), opens it with waitUntil load, prints through CDP Page.printToPDF so tagged output, outlines, header/footer templates and page numbers survive, emulates device metrics for sized screenshots, and writes in-page evaluations to files; when Aside is absent it runs the same spec through the browse daemon (newtab, load, js, pdf, screenshot, closetab) and reports ENGINE=aside|browse. bin/gstack-render.ts is the CLI skill templates call. lib/claude-bin.ts and lib/error-handling.ts become the canonical copies (browse/src re-exports them). Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…ehind the fallback Contract, cookbook, mode choice (aside repl by default, aside exec for reading), report format, the fallback section, and the full command reference carved on demand. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
QA_METHODOLOGY runs every phase as Aside scripts (orient, explore, document, re-test, mobile viewport via CDP emulation, links via HEAD fetch); the authenticate phase is 'you are already signed in'; a 13th rule requires consent before mutating actions on non-local targets; the fallback section translates each step onto $B. The qa E2E tests run on whichever engine is present. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
… plan-design-review, design-html drive Aside Design-system extraction is one script printing FONTS/COLORS/HEADINGS/TOUCH_TARGETS/NAV; competitor research confirms the exact URLs before opening them in the real browser and runs on the bundled browser when Aside is absent; design-html's viewport screenshots, sketches and comparison boards render through gstack-render. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…view drive Aside One aside repl script per page prints NAV/PAINT/LCP/RESOURCES/SCRIPTS/CSS/SUMMARY (benchmark), CONSOLE_ERRORS/NAV/TEXT + screenshot (canary, re-run every 60s), and the post-deploy check reads responseStatus from the navigation entry; each carries the $B fallback. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…visible browser stays the fallback
The readiness probe is lifted from {{ASIDE_SETUP}} at gen time (byte-identity pinned) and rule 3 points at browse/SKILL.md for how to drive; the consent question offers Aside first and gstack's own visible browser (handoff/resume for sign-in) as the fallback, as v1.72 framed it.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…ls runtime rides the fallback Look-then-extract scripts build the JSON inside the page and print it between JSON_START/JSON_END; aside exec for fuzzy intents; on the $B fallback the browser-skills match/prototype flow and /skillify apply as before. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…herwise asideClient.ts replaces the direct $B client with one render() call per PDF (the exact option mapping the browse pdf command had: paper, margins, header/footer/page numbers, tagged, outline, printBackground, preferCSSPageSize, Paged.js wait); the diagram pre-pass, oversized-image downscale and DOCX rasters each run as one render script with per-fence try/catch; exit 4 now means no browser is available and names both remedies; $P setup reports which engine it found. The e2e gates run on whichever engine is present, so the Linux lane exercises the fallback. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
SVG, PNG and excalidraw from one invocation over the content-addressed bundle staged under /tmp/gstack-render; every diagram type gets an excalidraw export; gstack-render picks the engine and prints ENGINE=; the diagram E2E gates on either engine. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
The planning, review, design, security and investigate skills research through {{ASIDE_RESEARCH}}; WebSearch stays in allowed-tools as the fallback; testing.ts's bootstrap step follows; skeleton ceilings ratcheted for the research block.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
setup gains _prune_stale_generated for every host tree and the doc generator removes gstack-* output dirs it did not write, so a skill removed from the source tree can never linger in an install. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…he $B fallback Touchfiles + E2E tiers gain the Aside keys, coverage matrix and eval baselines updated, size budget re-baselined to parity-baseline-v1.80.0.0.json (the contract plus fallback ride in every browsing skill), parity ceilings ratcheted with measured values, LLM-judge prompts and the E2E fixtures speak Aside-first, browse-fallback. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
README, BROWSER.md, docs/, CONTRIBUTING, CLAUDE.md, ARCHITECTURE, AGENTS.md, TODOS and the root router describe the one product story: Aside is the browser gstack drives first; the bundled headless browser is the automatic fallback (Linux, Windows, app closed) where cookie import, GStack Browser, pair-agent and browser-skills still apply. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…s, context-budget fixture bun run gen:skill-docs over the templates; goldens re-rendered; context-budget ceilings recaptured. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…ser is the fallback MINOR: new capability across ten skills, the renderer and research; nothing removed. CHANGELOG release summary + itemized changes; VERSION 1.80.0.0; package.json 1.80.0. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…ide; queue-advance release to v1.81.0.0 Both sides claimed v1.80.0.0, so VERSION, package.json and the agents digest auto-merged without a conflict; the release is re-versioned to the next free MINOR slot (bin/gstack-next-version), the size-budget baseline renamed to match, and the CHANGELOG carries the Aside-first entry above main's. Two semantic conflicts hidden in the clean setup auto-merge are resolved here: - _prune_stale_generated deleted a REAL host directory on banner-only proof; main's #2119 gate makes that weak proof file-scoped, so real dirs now go through _cleanup_weak_dir (SKILL.md, marker and our links only). - _browser_hint and the Chromium bootstrap summary now consult _PW_FAIL_REASON and Aside presence, so they never promise a bundled browser that cannot launch and never tell an Aside user their browser skills are gone. README, TESTING_INTERNALS and TODOS wording reconciled with the merged tree. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…pin follow-ups Two follow-ups from the /plan-ceo-review + /plan-eng-review pass on merging PR #2804 with main's v1.80.0.0 ownership gate: bring the Codex/Factory/ OpenCode/Cursor/Kiro copy loops and the stale-render prune under the .gstack-owned marker rule, and a free test pinning that the CHANGELOG top heading equals VERSION (the collision that git cannot see). Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Review army + adversarial passes (Claude and Codex) on the merged branch:
setup
- _prune_stale_generated scans the host dirs too (the generator already
removed the render before setup ran, so the host branch was dead), skips
symlinks in the render tree (rm -rf on a slash-terminated link empties its
target), removes a host symlink only when it resolves into gstack, cleans a
bannered real dir through _cleanup_weak_dir, recognizes frontmatter-renamed
skills, and logs through log. The always-run codex render passes every host
dir that may link to it.
- NEEDS_BUILD checks all three binaries (with $_EXE) and lib/ sources; the
browser hint and the bootstrap summary honor GSTACK_SKIP_ASIDE, treat a
requested skip as a request, and derive one skill list.
lib/aside-render.ts + bin/gstack-render.ts
- The loopback server carries a per-render secret path, checks containment on
the real path (symlink escapes are 403), and rejects malformed encoding.
- Inline eval results are one base64 line, so page text cannot forge
ASIDE_DIR= or the sentinel; the last ASIDE_DIR wins.
- runProc escalates SIGTERM to SIGKILL, bounds every wait, and clears every
timer (an uncleared one kept gstack-render alive after printing OK).
- renderTmpDir refuses a shared /tmp name owned by someone else; the work dir
and server are created inside try; goto's budget follows the render budget.
- probeAside classifies a present-but-failing CLI as ASIDE_NOT_RUNNING like
the skills' bash probe; render() retries on gstack's own browser when Aside
could not start or its private CDP bridge is gone (never on a page error
or a timeout of a running script); the CLI reports the engine that actually
rendered, exits 0 on --help, rejects non-numeric flags, documents
--wait-timeout, fences EVAL/PAGE_ERRORS as untrusted content, and names the
daemon's cookie-import JS lock remedy.
- The browse path passes --scale only when asked (a scale change rebuilds
the daemon context) and restores the viewport after a sized screenshot.
resolvers / templates
- The bash probe honors GSTACK_SKIP_ASIDE and has a perl deadline on stock
macOS; .local is no longer LOCAL (mDNS); same-origin filters compare parsed
origins; link status is HEAD-checked only on LOCAL targets; every
aside exec goes through the receipted _aside_exec prelude
({{ASIDE_EXEC_PRELUDE}}), including nine template blocks that called it
bare; the design sketch and diagram staging use private directories.
- The generator prunes only bannered renders and never a host whose
generation failed.
Docs, stale comments and dead code cleaned; goldens re-rendered; tests
updated and added for every behavior above.
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
… codes, and prose $B spans New free tests from the ship coverage audit: test/gstack-render-cli.test.ts (argv guards, --help, output contract with a fake daemon, failure and serve-root paths, no-browser case, prompt exit), test/setup-needs-build.test.ts (every binary and source set flips NEEDS_BUILD, Windows suffixes), make-pdf/test/cli-exit-codes.test.ts and setup-smoke.test.ts (error to exit code mapping, runSetup stages, renderPdf's engine), and prose-span cases for extractBrowseCommands in test/skill-parser.test.ts. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
BROWSER.md, ARCHITECTURE.md, CONTRIBUTING.md, README.md, CLAUDE.md,
docs/TESTING_INTERNALS.md and docs/PROJECT_STRUCTURE.md now describe the
shipped renderer and setup: the loopback render server's per-render secret
path and real-path containment, ENGINE= naming the engine that actually
rendered (mid-run retry on gstack's own browser), EVAL/PAGE_ERRORS fenced as
untrusted content, --wait-timeout and the CLI's argv guards, the receipted
_aside_exec prelude ({{ASIDE_EXEC_PRELUDE}} in the placeholder table), the
LOCAL host rule without .local, LOCAL-only HEAD checks in the links script,
GSTACK_SKIP_ASIDE across probe/renderer/setup, the ownership-gated
retired-skill prune, the widened NEEDS_BUILD check, and the new free tests
(gstack-render-cli, setup-prune-stale-generated, setup-browser-hint,
setup-needs-build, make-pdf cli-exit-codes and setup-smoke).
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…allback section browse/SKILL.md no longer has '## SETUP' / '## Core QA Patterns' (Aside is the primary driver; the $B block moved under 'Browser fallback'), so the gate test sliced an empty block and handed the agent nothing to run. Anchor on '### Find the `$B` binary' up to the next heading. 7/7 pass. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
|
😎 This pull request was merged. |
E2E Evals: ✅ PASS92/92 tests passed | $13.10 total cost | reconcile exit: 0 | ⚠ 2 flaky pass(es) — recorded, not blocking
Fail-closed reconciliationSliced lane: diff-selected gate census via scripts/test-paid-shards.ts (planner → 6 executors → fail-closed report) |
windows-free-tests: the gstack-render CLI tests drive a shebang fake browse that CreateProcess cannot exec, and two NEEDS_BUILD cases assert an execute bit and a bare-name miss that MSYS bash does not have (test -x ignores mode bits and resolves design -> design.exe). Those describes and cases now self-skip on win32; argument guards, --help, the no-browser case, and every other rebuild-check case still run there. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
… newtab retries once on a cold daemon A process whose pipes have reached EOF is exiting, but runProc gave the exit code only five seconds to arrive and then returned null, which run() reports as a failed command. Under CI's six-shard load one such render failed with the artifact already written. The SIGTERM/SIGKILL timers already bound the wait, so the exit race now runs to the kill deadline. The first CLI call auto-starts the browse daemon; on a cold start it can answer 'Unable to connect' once while the server is still coming up. That single case is retried after 1.5s; every other newtab failure is not. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
…res name the render error - Live fallback cases run 'goto about:blank' up to twice before asserting and skip (never fail) when the daemon cannot come up. - expectOk() puts r.error and the browse transcript into the assertion so a failed render is diagnosable from the CI log. - The argv-contract cases dump the fake's log on a miss. - File default timeout is 30s: the subject is the CLI contract, not latency. - Two cases pin the cold-daemon newtab retry and that other errors are not retried. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
… renderer Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Community PR #2804 by @time-attack, merged with main's v1.80.0.0, re-versioned to v1.81.0.0, and hardened by the pre-landing review. Every commit on the branch is covered below; the release entry in CHANGELOG.md is the user-facing story.
Aside-first browser driver (the PR, 16 commits by @time-attack)
scripts/resolvers/aside.ts: the Aside browser-driver contract ({{ASIDE_SETUP}}), cookbook ({{ASIDE_COOKBOOK}}), research block ({{ASIDE_RESEARCH}}), written from live probes against Aside CLI 1.26;{{BROWSE_FALLBACK}}maps every Aside step onto$Bso nothing regresses without Aside.lib/aside-render.ts+bin/gstack-render.ts: local-HTML rendering through Aside first, gstack's bundled browser otherwise (ENGINE=aside|browse); make-pdf,/diagram, design previews and/office-hourssketches use it./qa,/qa-only,/design-review,/design-consultation,/benchmark,/canary,/land-and-deploy,/devex-review,/scrape,/browsedrive Aside first; planning/review/security/investigate skills research through Aside's agent before WebSearch.setup+gen-skill-docsprune renders of skills that no longer exist;lib/claude-bin.tsandlib/error-handling.tsbecome canonical.Merge with main's v1.80.0.0 (1 merge commit)
setupauto-merge resolved in the merge itself: the prune honors main's fix(relink): don't clobber foreign skills that share a gstack name #2119 ownership gate; the browser hint and bootstrap summary honor_PW_FAIL_REASONand Aside presence.Pre-landing review fixes (1 commit) — see "Pre-Landing Review" below
Coverage tests (1 commit), CHANGELOG/TODOS (2 commits), docs sync (1 commit)
Test Coverage
Audit ran on the merged branch before the fix wave (report-only): 29/44 paths tested (66%), 15 gaps. The fix and test commits then closed the named gaps with hermetic fake-executable tests; the free suite grew from 8,834 to 8,972 tests across 537 files (all green, zero flaky retries, evidence-ledgered).
Coverage diagram (pre-fix-wave audit)
Every
[GAP]above except the two[→EVAL]prompt-block items now has a hermetic test (fakeaside/browseexecutables, anchor-slicedsetupblocks, spawned CLI); the two eval items are covered by the paid gate run below.Tests: 618 → 622 test files (+4 new:
test/gstack-render-cli.test.ts,test/setup-needs-build.test.ts,make-pdf/test/cli-exit-codes.test.ts,make-pdf/test/setup-smoke.test.ts); 5 existing test files extended (test/aside-render.test.ts(44 new cases),test/aside-driver.test.ts(11 new pins),test/setup-prune-stale-generated.test.ts,test/setup-browser-hint.test.ts,test/skill-parser.test.ts,test/gen-skill-docs-prune-stale.test.ts).Pre-Landing Review
Checklist pass + 7 specialists (testing, maintainability, security, performance, data-migration, api-contract, design) + red team + Claude adversarial subagent + Codex adversarial (contained run; this sandbox lacks bubblewrap so Codex's own sandbox could not execute commands — it ran read-only in a throwaway worktree with credentials scrubbed). 55 specialist findings (4 critical), 15 Claude-adversarial, 11 Codex-adversarial, 5 red-team. Applied in commit
444f8fef:gstack-*/glob matched symlinks andrm -rfon the slash-terminated name empties the link's TARGET. Now scans host dirs too, skips render-tree symlinks, removes a host symlink only when it resolves into gstack, cleans bannered real dirs via_cleanup_weak_dir, recognizes frontmatter-renamed skills (externalSkillName), logs throughlog; the always-run codex render passes every host dir.ASIDE_DIR=/sentinel; a page could redirect the artifact copy. Evals are one base64 line each; the lastASIDE_DIRwins; gstack-render fencesEVAL/PAGE_ERRORSas═══ UNTRUSTED WEB CONTENT ═══.gstack-renderalive up to 140s after printingOK— caught by the new tests).render()retries on gstack's own browser when Aside's CLI cannot start or its private_sendToTargetbridge is gone (never on a page error or a timeout); the CLI and make-pdf report the engine that actually rendered..localremoved from the LOCAL rule (mDNS = other LAN machines); same-origin filters compare parsed origins (https://example.com.attacker.tldpassedstartsWith); link status HEAD-checked only on LOCAL targets (on a real site every request carried the user's cookies); probe deadline viaperl alarmon stock macOS;GSTACK_SKIP_ASIDE=1honored by probe, setup and renderer; everyaside execgoes through the receipted_aside_execprelude ({{ASIDE_EXEC_PRELUDE}}), including nine template blocks that called it bare; design sketch and diagram staging use private directories.gstack-*dirs are ever removed.lib/(the moved canonical sources) was not in the staleness set;_EXEwas dead.--helpexit 0, non-numeric flags rejected,--wait-timeoutdocumented,--quietdoc matched to behavior; setup.ts failure names the remedy; stale references in find-browse.ts/AGENTS.md/BROWSER.md/SLOP_SCAN.md fixed; duplicated footer/tmp-dir/magic numbers consolidated.Deferred to TODOS.md (with rationale): make-pdf CSP for user documents rendered in the real browser profile (P1), diagram pre-pass memory cap (P1), fallback render vs the daemon's cookie-import JS lock (P2), carving the Aside contract into a shared section (P2),
$B jsenvelope (P2), perf/DRY items (P3),gen-skill-docs --dry-runwrite leak (P3), non-Claude host loops under the marker rule (P2), CHANGELOG-heading == VERSION pin (P3).Kept as-is, disclosed: the Aside path itself cannot execute on Linux (macOS-only; the contributor's macOS evidence and the self-skipping
test/skill-e2e-aside.test.tslane cover it; a read-only probe on the maintainer's Mac confirmed Aside CLI 1.26.902.1732 answersaside replin 220ms);codex review --basecould not run here (CLI rejects-s; its sandbox needs bubblewrap), so the Codex structured gate is informational.Design Review
Design specialist (lite) ran (SCOPE_FRONTEND=true from the diff scope): no user-visible UI changed (the only markup is a CDP print footer ported byte-for-byte). No findings. Codex design voice not run (see sandbox note above).
Eval Results
Gate tier (what CI runs per PR), sharded paid runner via
bun run eval:bg:gate(gstack-detach, lockgstack-evals): 50/50 shards executed — 49 passed, 1 failed, 0 timed out, 0 never started; selection was all 178 E2E + 25 LLM-judge tests becausetest/helpers/hermetic-env.tsis a global touchfile.test/skill-llm-eval.test.ts(LLM judge) passed.test/skill-e2e-bws.test.ts, was the PR's own doing: its three cases slice the$Bsetup block out ofbrowse/SKILL.mdbetween## SETUPand## Core QA Patterns, both gone since Aside became the primary driver, so the agent received an empty block. Anchors moved to the fallback section's### Find the $B binaryin2649a3b6; re-run alone: 7/7 pass.codex review --base(its sandbox needs bubblewrap, unavailable in this environment); Codex adversarial ran in a contained worktree instead.Scope Drift
Scope Check: CLEAN. Intent: land PR #2804 (Aside-first) against current main. Delivered: the PR plus the merge, the re-version, and review fixes that only tighten the PR's own surfaces (no new features). Two additions beyond the PR's scope are hardening the review demanded: the receipted
aside execwrapper and the loopback server's secret path.Plan Completion
Plan file audited by a fresh subagent: 45 items — 37 DONE, 2 CHANGED, 0 NOT DONE, 2 UNVERIFIABLE (session-performed process steps), 4 deferred by design (push/re-target, branch rename, paid evals, Aside-present E2E).
Contributed by @time-attack., baseline renamed); slot re-checked free before pushsetupsemantic fixes with tests;gen:skill-docs --host allclean; fullbun run buildexit 0GIT_EDITORprocess stepVerification Results
Skipped: no dev server (CLI + skill templates; nothing to browse).
/qadoes not apply.TODOS
No TODO items completed in this PR (the PR itself marks the "QA logged-in-evidence path via Aside (Phase 2)" item as landed). Filed: 2 follow-ups from the plan reviews and 8 from the pre-landing review (see TODOS.md, "Aside-first follow-ups" and NEXT PRIORITY).
Documentation
Post-ship doc sync for the v1.81.0.0 review fixes (docs commit
97fc8808). No SKILL.md/.tmpl touched; CHANGELOG, VERSION and TODOS untouched by the sync (the 1.81.0.0 entry already covers the fix wave).BROWSER.md:gstack-renderoutput contract (ENGINE=names the engine that actually rendered; retry on gstack's own browser only when Aside's CLI cannot start or its CDP bridge is missing),EVAL/PAGE_ERRORSfenced as untrusted web content,--wait-timeout,--helpexit 0, numeric-flag guards; the loopback server's per-render secret path and real-path containment; LOCAL rule without*.local; LOCAL-only HEAD checks; receipted_aside_exec; 30s probe bound;GSTACK_SKIP_ASIDE=1; audit-trail and CI bullets corrected.ARCHITECTURE.md: same render facts;{{ASIDE_EXEC_PRELUDE}}row; research paragraph notes the receipt.CONTRIBUTING.md: render guidance points atrender()with the engine-specific halves; exported test seams (pickEngine(fresh, deps),serveDir,SAFE_TMP_DIR,PAGE_NUMBER_FOOTER); new Tier-1 test bullets; rebuild rule = three binaries +lib/; the prune's ownership gate;GSTACK_SKIP_ASIDE.CLAUDE.md: ownership gate covers the retired-skill prune and pins its test.README.md: troubleshooting addsGSTACK_SKIP_ASIDE=1and theENGINE=first line.docs/TESTING_INTERNALS.md,docs/PROJECT_STRUCTURE.md: E2E gating corrected; new anchor-sliced setup tests and the CLI test listed.Codex documentation review: 9 gaps, each verified against code, all fixed in the same commit. Documentation debt (reference-only, no how-to yet):
GSTACK_SKIP_ASIDE=1,gstack-renderflags, the exported test seams,{{ASIDE_EXEC_PRELUDE}}.Test plan
bun run gen:skill-docs --host all && git diff --exit-codeclean; ship goldens re-renderedbun run build(all binaries) exit 0🤖 Generated with Claude Code
Open workspace in Conductor